package service

import (
	"context"
	"fmt"
	"math"
	"mini-app/config/redis"
	"mini-app/internal/app/grpc/client"
	"mini-app/internal/app/grpc/protoc/advertisingc"
	"mini-app/internal/dal"
	"mini-app/internal/dao"
	"mini-app/internal/define"
	"mini-app/internal/pkg"
	"strconv"
	"strings"
	"time"

	"192.168.1.75/go-pkg/errorx"
	"192.168.1.75/go-pkg/helper"
	"192.168.1.75/go-pkg/logx"
	"github.com/go-pay/gopay/wechat/v3"
	"github.com/shopspring/decimal"
)

type Advertisement struct{}

type CreateAdOrderRes struct {
	ID []string `json:"id"`
}

type Material struct {
	MaterialID      string `json:"material_id"`
	FilePath        string `json:"file_path"`
	Name            string `json:"name"`
	Type            int8   `json:"type"`
	Duration        int64  `json:"duration"`
	RepeatTimes     int64  `json:"repeat_times"`
	PlayType        int32  `json:"play_type"`
	RegularInterval int32  `json:"regular_interval"`
	// DeviceHasMaterialCount int    `gorm:"-" json:"device_hasmaterial_count"`
	// DeviceHasMaterial      string `gorm:"-" json:"device_hasmaterial"`
}

type OrderItem struct {
	ID              string     `json:"id"`
	CreatedAt       int64      `json:"created_at"`
	CustomName      string     `json:"custom_name"`
	PhoneNumber     string     `json:"phone_number"`
	DeviceIDs       string     `json:"device_ids"`
	StartAt         int64      `json:"start_at"`
	EndAt           int64      `json:"end_at"`
	Status          int        `json:"pay_status"`
	Remark          string     `json:"remark"`
	OpenID          string     `json:"openid"`
	AdvertisementID string     `json:"advertisement_id"`
	PayAmount       float32    `json:"pay_amount"`
	PaidAmount      float32    `json:"paid_amount"`
	PaidID          string     `json:"paid_id"`
	DiscountAmount  float32    `json:"discount_amount"`
	ScheduleID      string     `json:"schedule_id"`
	ScheduleStatus  int        `json:"schedule_status"`
	Materials       []Material `gorm:"-" json:"materials"`
}

// 登录获取openid
func (Advertisement) Login(ctx context.Context, code string) (token, phone string, err error) {

	logx.Info(context.Background(), "Advertisement Login", logx.Any("code", code))
	miniSDK, err := pkg.MiniProgram{}.NewAdvertisement()
	if err != nil {

		logx.Info(context.Background(), "Advertisement Login", logx.Any("err", ""))
		return
	}
	logx.Info(context.Background(), "Advertisement Code2Session", logx.Any("code", string(code)))
	rsp, err := miniSDK.GetAuth().Code2Session(code)
	if err != nil || rsp.ErrCode != 0 {
		return "", "", errorx.New("登录授权失败", -1)
	}

	// openid及sesion_key存入redis
	rds := redis.NewDB()
	token = helper.Md5(strconv.Itoa(int(time.Now().UnixNano())) + helper.RandString(32))

	logx.Info(context.Background(), "Advertisement redis", logx.Any("token", string(token)))

	rds.Set(ctx, define.MiniAppSessionOpenid+token, rsp.OpenID, time.Duration(2*24)*time.Hour).Result()  // openid
	rds.Set(ctx, define.MiniAppSessionKey+token, rsp.SessionKey, time.Duration(2*24)*time.Hour).Result() // 会话密钥session_key

	// var channelID string
	// cli, err := client.GetDeviceAdminClient()
	// if cli != nil && err == nil {
	// 	deviceDetail, err := cli.DeviceDetail(ctx, &devicec.DeviceDetailReq{IdentificationCode: salesID})
	// 	if err == nil && deviceDetail.Device != nil {
	// 		// 渠道信息
	// 		channelID, err = service.PromotionChannel{}.GetChannelByRobotID(ctx, dal.Q, deviceDetail.Device.RobotId)
	// 		if err != nil {
	// 			channelID = ""
	// 		}
	// 	}
	// }
	channelID := "advertisement"
	// 用户信息写入表中
	userInfo, userErr := dao.User{}.UserInfo(ctx, dal.Q, rsp.OpenID, "", "")
	if userErr != nil || userInfo == nil {
		dao.User{}.Create(ctx, dal.Q, rsp.OpenID, channelID)
		phone = ""
	} else {
		if channelID != "" && userInfo.ChannelID == "" {
			dao.User{}.UpdateChannelID(ctx, dal.Q, rsp.OpenID, channelID)
		}
		phone = userInfo.Phone
	}
	return
}

// 获取手机号
func (Advertisement) GetPhoneNumber(ctx context.Context, openid, code string) (phone string, err error) {

	miniSDK, err := pkg.MiniProgram{}.NewAdvertisement()
	if err != nil {
		return
	}
	// PhoneNumber     手机号（国外手机号会有区号）
	// PurePhoneNumber 无区号的手机号
	phoneRsp, phoneErr := miniSDK.GetAuth().GetPhoneNumber(code)
	if phoneErr != nil || phoneRsp == nil || phoneRsp.ErrCode != 0 {
		err = errorx.New("手机号获取失败")
		return
	}

	// 查询用户信息
	userInfo, err := dao.User{}.UserInfo(ctx, dal.Q, openid, "", "")
	if err != nil || userInfo == nil {
		err = errorx.New("用户信息不存在")
		return
	}
	// 保存手机号
	err = dao.User{}.UpdatePhone(ctx, dal.Q, openid, phoneRsp.PhoneInfo.PurePhoneNumber)
	return phoneRsp.PhoneInfo.PurePhoneNumber, err
}

// 创建订单
func (Advertisement) CreateOrder(ctx context.Context, openID, customName, phoneNumber, deviceIDs string, startTime, endTime int64) (ids []string, err error) {

	// 检查一分钟内是否已经下单
	lastOrder, err := dao.Advertisement{}.GetLastOrderByOpenID(ctx, dal.Q, openID)
	if err == nil && lastOrder != nil {
		// 如果存在订单且创建时间在一分钟内,则拒绝创建
		if time.Now().Unix()-lastOrder.CreatedAt < 60 {
			err = errorx.New("一分钟内只能下一个订单")
			return
		}
	}
	// 写入订单表
	ID, _ := helper.UUID{}.String()
	basePrice, err := AdConfig{}.GetBasePrice(ctx)

	deviceIDsep := strings.Split(deviceIDs, ",")

	deviceIDs_Input := ""
	for _, deviceIDAndInfo := range deviceIDsep {
		deviceIDOnly := strings.Split(deviceIDAndInfo, ":")[0]
		deviceIDs_Input += deviceIDOnly
		deviceIDs_Input += ","
	}

	totalPrice, err := AdCoupon{}.GetTotalPriceByCoupon(ctx, startTime, endTime, deviceIDs_Input, "")

	duration := endTime - startTime
	// Convert duration from seconds to days, rounding up
	durationDays := int64((duration + 86399) / 86400) // 86400 seconds in a day, add 86399 to round up

	if durationDays <= 0 {
		err = errorx.New("广告投放时间必须大于0天")
		return
	}

	deviceIDsLen := len(deviceIDsep)

	// Calculate payment: 300 per device per day
	paymentAmountWithoutCoupon := float32(basePrice) * float32(deviceIDsLen) * float32(durationDays)

	paymentAmount := totalPrice
	discountAmount := paymentAmountWithoutCoupon - paymentAmount

	dao.Advertisement{}.Create(ctx, dal.Q, ID, openID, customName, phoneNumber, deviceIDs, "", "", discountAmount, startTime, endTime)
	ids = append(ids, ID)

	logx.Info(context.Background(), "Advertisement CreateOrder", logx.Any("ID", ID))
	logx.Info(context.Background(), "Advertisement CreateOrder", logx.Any("basePrice", basePrice))
	logx.Info(context.Background(), "Advertisement CreateOrder", logx.Any("paymentAmount", paymentAmount))
	logx.Info(context.Background(), "Advertisement CreateOrder", logx.Any("deviceIDsLen", deviceIDsLen))
	logx.Info(context.Background(), "Advertisement CreateOrder", logx.Any("durationDays", durationDays))
	dao.Advertisement{}.OrderPayAmountChange(ctx, dal.Q, ID, paymentAmount)

	return
}

func (Advertisement) CreateOrderBySchedule(ctx context.Context, openID, customName, phoneNumber, deviceIDs, scheduleID, merchantID, supportActivityID string) (ids []string, err error) {

	// 检查一分钟内是否已经下单
	lastOrder, err := dao.Advertisement{}.GetLastOrderByOpenID(ctx, dal.Q, openID)
	if err == nil && lastOrder != nil {
		// 如果存在订单且创建时间在一分钟内,则拒绝创建
		if time.Now().Unix()-lastOrder.CreatedAt < 60 {
			err = errorx.New("一分钟内只能下一个订单")
			return
		}
	}
	// 写入订单表
	ID, _ := helper.UUID{}.String()
	basePrice, err := AdConfig{}.GetBasePrice(ctx)

	client, err := client.GetAdvertisingClient()
	if err != nil {
		return
	}
	var params advertisingc.SPublishScheduleDetailReq
	params.Id = scheduleID
	params.MerchantId = merchantID
	resp, err := client.ScheduleDetail(ctx, &params)
	if err != nil {
		return
	}

	startTime := resp.Data.StartTime
	endTime := resp.Data.EndTime

	//这里用传入的deviceIDs
	// deviceIDs := resp.Data.Devices
	// deviceIDs_Input := ""
	// for _, deviceID := range deviceIDs {

	// 	deviceIDs_Input += deviceID
	// 	deviceIDs_Input += ","
	// }

	deviceIDsep := strings.Split(deviceIDs, ",")
	deviceIDs_Input := ""
	for _, deviceIDAndInfo := range deviceIDsep {
		deviceIDOnly := strings.Split(deviceIDAndInfo, ":")[0]
		deviceIDs_Input += deviceIDOnly
		deviceIDs_Input += ","
	}

	totalPrice, err := AdCoupon{}.GetTotalPriceByCoupon(ctx, startTime, endTime, deviceIDs_Input, "")

	duration := endTime - startTime
	// Convert duration from seconds to days, rounding up
	durationDays := int64((duration + 86399) / 86400) // 86400 seconds in a day, add 86399 to round up

	if durationDays <= 0 {
		err = errorx.New("广告投放时间必须大于0天")
		return
	}

	deviceIDsLen := len(deviceIDsep)

	// Calculate payment: 300 per device per day
	paymentAmountWithoutCoupon := float32(basePrice) * float32(deviceIDsLen) * float32(durationDays)

	paymentAmount := totalPrice
	discountAmount := paymentAmountWithoutCoupon - paymentAmount

	dao.Advertisement{}.Create(ctx, dal.Q, ID, openID, customName, phoneNumber, deviceIDs, scheduleID, supportActivityID, discountAmount, startTime, endTime)
	ids = append(ids, ID)

	logx.Info(context.Background(), "Advertisement CreateOrderBySchedule", logx.Any("ID", ID))
	logx.Info(context.Background(), "Advertisement CreateOrderBySchedule", logx.Any("basePrice", basePrice))
	logx.Info(context.Background(), "Advertisement CreateOrderBySchedule", logx.Any("paymentAmount", paymentAmount))
	logx.Info(context.Background(), "Advertisement CreateOrderBySchedule", logx.Any("deviceIDsLen", deviceIDsLen))
	logx.Info(context.Background(), "Advertisement CreateOrderBySchedule", logx.Any("durationDays", durationDays))
	dao.Advertisement{}.OrderPayAmountChange(ctx, dal.Q, ID, paymentAmount)

	var params2 advertisingc.SPublishScheduleSetOrderIDReq
	params2.Id = scheduleID
	params2.OrderId = ID
	params2.PayAmount = paymentAmount
	params2.PaidAmount = 0
	params2.DiscountAmount = discountAmount
	params2.CustomName = customName
	params2.PhoneNumber = phoneNumber
	_, err = client.ScheduleSetOrderID(ctx, &params2)
	if err != nil {
		return
	}
	return
}

// 订单列表
func (Advertisement) OrderList(ctx context.Context, ID, openid string, orderStatus int, startTime, endTime int64, customName, phoneNumber string, scheduleStatus int, supportActivityID string, page, limit int) (
	data []OrderItem, total int64, err error,
) {
	orders, total, err := dao.Advertisement{}.OrderList(ctx, dal.Q, ID, openid, orderStatus, startTime, endTime, customName, phoneNumber, scheduleStatus, supportActivityID, page, limit)

	client, err := client.GetAdvertisingClient()
	if err != nil {
		return
	}
	if err == nil && total > 0 {
		for _, order := range orders {
			var params advertisingc.SPublishScheduleDetailReq
			params.Id = order.ScheduleID
			params.MerchantId = ""
			resp, err1 := client.ScheduleDetail(ctx, &params)
			if err1 != nil {
				return
			}

			var item OrderItem
			item.ID = order.ID
			item.CreatedAt = order.CreatedAt
			item.CustomName = order.CustomName
			item.PhoneNumber = order.PhoneNumber
			item.DeviceIDs = order.DeviceIDs
			item.StartAt = order.StartAt
			item.EndAt = order.EndAt
			item.Status = order.Status
			item.Remark = order.Remark
			item.OpenID = order.OpenID
			item.AdvertisementID = order.AdvertisementID
			item.PayAmount = order.PayAmount
			item.PaidAmount = order.PaidAmount
			item.PaidID = order.PaidID
			item.DiscountAmount = order.DiscountAmount
			item.ScheduleID = order.ScheduleID

			if resp.Data != nil {
				materials := resp.Data.GetMaterials()
				item.ScheduleStatus = int(resp.Data.Status)

				mats := []Material{}
				for _, v := range materials {
					mat := Material{
						MaterialID:      v.MaterialId,
						FilePath:        v.FilePath,
						Name:            v.Name,
						Type:            int8(v.Type),
						Duration:        v.Duration,
						RepeatTimes:     v.RepeatTimes,
						PlayType:        v.PlayType,
						RegularInterval: v.RegularInterval,
					}

					mats = append(mats, mat)
				}
				item.Materials = mats
			}

			data = append(data, item)
		}

	}
	return
}

// 订单详情
func (Advertisement) OrderDetail(ctx context.Context, ID string) (data OrderItem, err error) {
	order, err := dao.Advertisement{}.Detail(ctx, dal.Q, ID)

	client, err := client.GetAdvertisingClient()
	if err != nil {
		return
	}
	var params advertisingc.SPublishScheduleDetailReq
	params.Id = order.ScheduleID
	params.MerchantId = ""
	resp, err := client.ScheduleDetail(ctx, &params)
	if err != nil {
		return
	}

	materials := resp.Data.GetMaterials()

	if err == nil {
		data.ID = order.ID
		data.CreatedAt = order.CreatedAt
		data.CustomName = order.CustomName
		data.PhoneNumber = order.PhoneNumber
		data.DeviceIDs = order.DeviceIDs
		data.StartAt = order.StartAt
		data.EndAt = order.EndAt
		data.Status = order.Status
		data.Remark = order.Remark
		data.OpenID = order.OpenID
		data.AdvertisementID = order.AdvertisementID
		data.PayAmount = order.PayAmount
		data.PaidAmount = order.PaidAmount
		data.PaidID = order.PaidID
		data.DiscountAmount = order.DiscountAmount
		data.ScheduleID = order.ScheduleID
		mats := []Material{}
		for _, v := range materials {
			mat := Material{
				MaterialID:      v.MaterialId,
				FilePath:        v.FilePath,
				Name:            v.Name,
				Type:            int8(v.Type),
				Duration:        v.Duration,
				RepeatTimes:     v.RepeatTimes,
				PlayType:        v.PlayType,
				RegularInterval: v.RegularInterval,
			}

			mats = append(mats, mat)
		}

		data.Materials = mats
	}
	return
}

func (Advertisement) OrderModify(ctx context.Context, ID string, Status int, AdvertisementID, Remark string) (err error,
) {
	err = dao.Advertisement{}.OrderRemarkChange(ctx, dal.Q, ID, Status, AdvertisementID, Remark)
	if err == nil {

	}
	return
}

// 微信支付
func (Advertisement) WechatJSPay(ctx context.Context, ID, openid string) (data wechat.JSAPIPayParams, err error) {

	logx.Info(context.Background(), "WechatJSPay", logx.Any("orderID", ID))
	logx.Info(context.Background(), "WechatJSPay", logx.Any("openid", openid))

	orderDetail, err := dao.Advertisement{}.Detail(ctx, dal.Q, ID)

	logx.Info(context.Background(), "WechatJSPay", logx.Any("orderDetail", orderDetail.ID))
	if orderDetail.ID == "" {
		err = errorx.New("订单不存在", -1)
		return
	}
	if orderDetail.Status != define.AdOrderStatusUnpaid {
		err = errorx.New("当前订单状态不支持支付", -1)
		return
	}

	// 微信支付初始化
	pkg.WechatPay{}.V3ConfigInit("", "", "")

	paymentAmount := int64(math.Round(float64(orderDetail.PayAmount * 100)))

	logx.Info(context.Background(), "WechatJSPay", logx.Any("pay_univalent", fmt.Sprint(paymentAmount)))

	if paymentAmount <= 0 {
		err = errorx.New("当前订单金额错误", -1)
		return
	}

	jsapiRsp, err := pkg.WechatPay{}.V3TransactionJsapiForAdvertisement(ctx, pkg.GenerateRanderOrderID(ID), openid, paymentAmount, "广告小程序")
	if err != nil {
		logx.Error(ctx, "订单微信支付错误", logx.Any("订单号", orderDetail.ID), logx.Any("error", err))
		// err = errorx.New("请联系客服小姐姐进行投放。点击首页或设备详情页“客服”按钮即可呀~")
	}

	if jsapiRsp == nil {
		logx.Error(ctx, "WechatJSPay", logx.Any("jsapiRsp", " is nil"))
		// err = errorx.New("请联系客服小姐姐进行投放。点击首页或设备详情页“客服”按钮即可呀~")
		return data, err
	}

	return *jsapiRsp, err
}

func (Advertisement) Refund(ctx context.Context, outTradeNo string, remarks string, userID, userName string) (refundCode int, err error) {
	err = pkg.WechatPay{}.V3ConfigInit("", "", "")
	if err != nil {
		logx.Info(ctx, "Refund", logx.Any("V3ConfigInit err", err))
		return
	}
	orderID := pkg.ExtractOrderID(outTradeNo)
	logx.Info(ctx, "Refund", logx.Any("orderID", orderID), logx.Any("outTradeNo", outTradeNo))
	if orderID != "" {
		data, err := dao.Advertisement{}.Detail(ctx, dal.Q, orderID)
		if err == nil {
			PaidAmount := decimal.NewFromFloat32(data.PaidAmount).Mul(decimal.NewFromInt(100)).IntPart()
			wxpayRsp, wxpayErr := pkg.WechatPay{}.V3Refund(ctx, outTradeNo, outTradeNo, PaidAmount, PaidAmount)
			if wxpayErr != nil {
				logx.Error(ctx, "Refund", logx.Any("wxpayErr", wxpayErr))
				return 0, wxpayErr
			}
			// Create refund record
			err = dao.AdRefundDao{}.Create(ctx, dal.Q, orderID, PaidAmount, remarks, outTradeNo, userID, userName)
			if err != nil {
				return 0, err
			}

			err = dao.Advertisement{}.OrderStatusChange(ctx, dal.Q, orderID, define.AdOrderStatusRefund)
			if err != nil {
				return 0, err
			}
			return wxpayRsp.Code, nil
		}
	}

	return
}

type RefundOrderInfo struct {
	RefundID        string `json:"refund_id"`
	OrderID         string `json:"order_id"`
	RefundAmount    int64  `json:"refund_amount"`
	RefundRemark    string `json:"refund_remark"`
	RefundCreatedAt int64  `json:"refund_created_at"`
	RefundPaidID    string `json:"refund_paid_id"`
	RefundOpenID    string `json:"refund_openid"`
	RefundUserID    string `json:"refund_userid"`
	RefundUserName  string `json:"refund_username"`

	// Advertisement 字段
	AdID            string  `json:"ad_id"`
	AdCreatedAt     int64   `json:"ad_created_at"`
	CustomName      string  `json:"custom_name"`
	PhoneNumber     string  `json:"phone_number"`
	DeviceIDs       string  `json:"device_ids"`
	StartAt         int64   `json:"start_at"`
	EndAt           int64   `json:"end_at"`
	Status          int     `json:"pay_status"`
	Remark          string  `json:"remark"`
	OpenID          string  `json:"openid"`
	AdvertisementID string  `json:"advertisement_id"`
	PayAmount       float32 `json:"pay_amount"`
	PaidAmount      float32 `json:"paid_amount"`
	PaidID          string  `json:"paid_id"`
	DiscountAmount  float32 `json:"discount_amount"`
	ScheduleID      string  `json:"schedule_id"`

	Materials []Material `gorm:"-" json:"materials"`

	// Schedule 字段 (来自 resp.Data)
	ScheduleName      string   `json:"schedule_name"`
	Position          int32    `json:"position"`
	PublishType       int32    `json:"publish_type"`
	PublishCount      int64    `json:"publish_count"`
	ScheduleStartTime int64    `json:"schedule_start_time"`
	ScheduleEndTime   int64    `json:"schedule_end_time"`
	ScheduleDuration  int64    `json:"schedule_duration"`
	Details           string   `json:"details"`
	ScheduleStatus    int32    `json:"schedule_status"`
	DistrictID        string   `json:"district_id"`
	LocationID        string   `json:"device_location"`
	Gender            string   `json:"gender"`
	Age               string   `json:"age"`
	Tag               string   `json:"tag"`
	MerchantID        string   `json:"merchant_id"`
	MerchantName      string   `json:"merchant_name"`
	CreateUser        string   `json:"create_user"`
	CreateUsername    string   `json:"create_username"`
	ScheduleCreatedAt int64    `json:"schedule_created_at"`
	ScheduleDeletedAt int64    `json:"schedule_deleted_at"`
	Devices           []string `json:"devices"`
	DetailsShow       int32    `json:"details_show"`
	Orientation       int32    `json:"orientation"`
	// DeviceLocation    int32    `json:"device_location"`
}

func (Advertisement) RefundList(ctx context.Context, order_id string, start_time, end_time int64, openid string, userid, username string, page, limit int) (items []RefundOrderInfo, total int64, err error) {

	list, total, err := dao.AdRefundDao{}.List(ctx, dal.Q, order_id, start_time, end_time, openid, userid, username, page, limit)

	client, err := client.GetAdvertisingClient()
	if err != nil {
		return
	}
	for _, refund := range list {
		var item RefundOrderInfo
		item.RefundID = refund.ID
		item.OrderID = refund.OrderID
		item.RefundAmount = refund.Amount
		item.RefundRemark = refund.Remark
		item.RefundCreatedAt = refund.CreatedAt
		item.RefundPaidID = refund.PaidID
		item.RefundOpenID = refund.OpenID
		item.RefundUserID = refund.UserID
		item.RefundUserName = refund.UserName

		// 通过 orderID 查询订单详情
		order, err1 := dao.Advertisement{}.Detail(ctx, dal.Q, refund.OrderID)
		if err1 != nil {
			// 如果查询订单失败，只填充退款信息，订单字段留空
			items = append(items, item)
			continue
		}

		// 填充订单信息
		if order != nil {
			item.AdID = order.ID
			item.AdCreatedAt = order.CreatedAt
			item.CustomName = order.CustomName
			item.PhoneNumber = order.PhoneNumber
			item.DeviceIDs = order.DeviceIDs
			item.StartAt = order.StartAt
			item.EndAt = order.EndAt
			item.Status = order.Status
			item.Remark = order.Remark
			item.OpenID = order.OpenID
			item.AdvertisementID = order.AdvertisementID
			item.PayAmount = order.PayAmount
			item.PaidAmount = order.PaidAmount
			item.PaidID = order.PaidID
			item.DiscountAmount = order.DiscountAmount
			item.ScheduleID = order.ScheduleID

			var params advertisingc.SPublishScheduleDetailOrderInfoReq
			params.Id = order.ScheduleID
			params.MerchantId = ""
			resp, err2 := client.ScheduleDetailOrderInfo(ctx, &params)
			if err2 != nil {
				return nil, 0, err2
			}

			// 将 resp.Data 的字段赋值给 item
			if resp.Data != nil {
				item.ScheduleName = resp.Data.Name
				item.Position = resp.Data.Position
				item.PublishType = resp.Data.PublishType
				item.PublishCount = resp.Data.PublishCount
				item.ScheduleStartTime = resp.Data.StartTime
				item.ScheduleEndTime = resp.Data.EndTime
				item.ScheduleDuration = resp.Data.Duration
				item.Details = resp.Data.Details
				item.ScheduleStatus = resp.Data.Status
				item.DistrictID = resp.Data.DistrictId
				item.LocationID = resp.Data.LocationId
				item.Gender = resp.Data.Gender
				item.Age = resp.Data.Age
				item.Tag = resp.Data.Tag
				item.MerchantID = resp.Data.MerchantId
				item.MerchantName = resp.Data.MerchantName
				item.CreateUser = resp.Data.CreateUser
				item.CreateUsername = resp.Data.CreateUsername
				item.ScheduleCreatedAt = resp.Data.CreatedAt
				item.ScheduleDeletedAt = resp.Data.DeletedAt
				item.Devices = resp.Data.Devices
				item.DetailsShow = resp.Data.DetailsShow
				item.Orientation = resp.Data.Orientation

				materials := resp.Data.GetMaterials()
				mats := []Material{}
				for _, v := range materials {
					mat := Material{
						MaterialID:      v.MaterialId,
						FilePath:        v.FilePath,
						Name:            v.Name,
						Type:            int8(v.Type),
						Duration:        v.Duration,
						RepeatTimes:     v.RepeatTimes,
						PlayType:        v.PlayType,
						RegularInterval: v.RegularInterval,
					}

					mats = append(mats, mat)
				}

				item.Materials = mats
			}

		}
		items = append(items, item)
	}
	return items, total, nil
}
